# Copyright 2012 Google Inc. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

"""Tests for easy_filter.py."""

__author__ = 'jbenjamin@google.com (Jason Debolt)'

import datetime
import easy_filter
import unittest


class EasyFilterTest(unittest.TestCase):
  """Tests related to the EasyFilter class."""

  def setUp(self):
    """Create a list of Foo objects for testing the EasyFilter class."""
    self.a = Foo('all', datetime.date(1, 1, 1), datetime.date(1, 1, 1), 27)
    self.b = Foo('your', datetime.date(5, 5, 5), datetime.date(2, 2, 2), 30)
    self.c = Foo('base', datetime.date(5, 5, 5), datetime.date(3, 3, 3), 27)
    self.d = Foo('base', datetime.date(3, 3, 3), datetime.date(3, 3, 3), 28)
    self.e = Foo('are', datetime.date(3, 3, 3), datetime.date(3, 3, 3), 29)
    self.f = Foo('belong', datetime.date(4, 4, 4), datetime.date(4, 4, 4), 29)
    self.g = Foo('us', datetime.date(5, 5, 5), datetime.date(5, 5, 5), 27)
    self.h = Foo('us', datetime.date(5, 5, 5), datetime.date(5, 5, 5), 30)
    self.i = Foo('us', datetime.date(6, 6, 6), datetime.date(6, 6, 6), 31)
    self.items = [
        self.a, self.b, self.c, self.d, self.e, self.f, self.g, self.h, self.i]

  def testIsValidIsTrue(self):
    """Tests that the correct result is returned."""
    self.a._is_valid = True
    self.assertTrue(self.a.IsValid())
    self.assertTrue(self.a._is_valid)

  def testIsValidIsFalse(self):
    """Tests that the correct result is returned."""
    self.a._is_valid = False
    self.assertFalse(self.a.IsValid())
    self.assertTrue(self.a._is_valid)

  def testFilterByName(self):
    """Tests that a result is returned."""
    self.assertTrue(self.a.Filter(name='all').IsValid())

  def testFilterByNameAndAge(self):
    """Tests that a result is returned."""
    self.assertTrue(self.i.Filter(name='us', age=31).IsValid())

  def testFilterByNameAndAgeWithChaining(self):
    """Tests that a result is returned."""
    self.assertTrue(self.i.Filter(name='us').Filter(age=31).IsValid())

  def testFilterByNameAndDate(self):
    """Tests that a result is returned."""
    self.assertTrue(
        self.g.Filter(name='us', date=datetime.date(5, 5, 5)).IsValid())
    self.assertTrue(
        self.h.Filter(name='us', date=datetime.date(5, 5, 5)).IsValid())

  def testFilterByNameAndDateWithChaining(self):
    """Tests that a result is returned."""
    self.assertTrue(
        self.g.Filter(name='us').Filter(date=datetime.date(5, 5, 5)).IsValid())
    self.assertTrue(
        self.h.Filter(name='us').Filter(date=datetime.date(5, 5, 5)).IsValid())

  def testFilterBySingleReturnsSingleResult(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter(name='all').IsValid() for i in self.items],
                     [1, 0, 0, 0, 0, 0, 0, 0, 0])

  def testFilterBySingleReturnsSingleResultUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter('OR', name='all').IsValid() for i in self.items],
                     [1, 0, 0, 0, 0, 0, 0, 0, 0])

  def testFilterBySingleReturnsSingleResultUsingAndModeExplicitly(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('AND', name='all').IsValid() for i in self.items],
        [1, 0, 0, 0, 0, 0, 0, 0, 0])

  def testFilterBySingleReturnsMultipleResults(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter(name='us').IsValid() for i in self.items],
                     [0, 0, 0, 0, 0, 0, 1, 1, 1])

  def testFilterBySingleReturnsMultipleResultsUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter('OR', name='us').IsValid() for i in self.items],
                     [0, 0, 0, 0, 0, 0, 1, 1, 1])

  def testFilterBySingleReturnsMultipleResultsUsingAndModeExplicitly(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter('AND', name='us').IsValid() for i in self.items],
                     [0, 0, 0, 0, 0, 0, 1, 1, 1])

  def testFilterByMultipleReturnsSingleResult(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='base', age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleReturnsSingleResultWithChaining(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='base').Filter(age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleReturnsSingleResultUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name='base', age=27).IsValid() for i in self.items],
        [1, 0, 1, 1, 0, 0, 1, 0, 0])

  def testFilterByMultipleReturnsSingleResultUsingAndModeExplicitly(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('AND', name='base', age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleReturnsMultipleResults(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual(
        [i.Filter(name='us', date=dt).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 1, 1, 0])

  def testFilterByMultipleReturnsMultipleResultsWithChaining(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual(
        [i.Filter(name='us').Filter(date=dt).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 1, 1, 0])

  def testFilterByMultipleReturnsMultipleResultsUsingOrMode(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual(
        [i.Filter('OR', name='us', date=dt).IsValid() for i in self.items],
        [0, 1, 1, 0, 0, 0, 1, 1, 1])

  def testFilterByMultipleReturnsMultipleResultsUsingAndModeExplicitly(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual(
        [i.Filter('AND', name='us', date=dt).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 1, 1, 0])

  def testFilterBySingleWithSingleTuple(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name=('base', 'us')).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterBySingleWithSingleTupleUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name=('base', 'us')).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterBySingleWithSingleTupleUsingAndModeExplicitly(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('AND', name=('base', 'us')).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterByMultipleWithSingleTuple(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name=('base', 'us'), age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleWithSingleTupleWithChaining(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter(name=t).Filter(age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleWithSingleTupleUsingOrMode(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter('OR', name=t, age=27).IsValid() for i in self.items],
        [1, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterByMultipleWithSingleTupleUsingAndModeExplicilty(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter('AND', name=t, age=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleWithMultipleTuples(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter(name=t, age=(27, 28, 30)).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 0])

  def testFilterByMultipleWithMultipleTuplesWithChaining(self):
    """Tests that the correct result is returned."""
    tup = (27, 28, 30)
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter(name=t).Filter(age=tup).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 0])

  def testFilterByMultipleWithMultipleTuplesUsingOrMode(self):
    """Tests that the correct result is returned."""
    age_t = (27, 28, 30)
    name_t = ('base', 'us')
    self.assertEqual(
        [i.Filter('OR', name=name_t, age=age_t).IsValid() for i in self.items],
        [1, 1, 1, 1, 0, 0, 1, 1, 1])

  def testFilterByMultipleWithMultipleTuplesUsingAndModeExplicilty(self):
    """Tests that the correct result is returned."""
    age_t = (27, 28, 30)
    name_t = ('base', 'us')
    self.assertEqual(
        [i.Filter('AND', name=name_t, age=age_t).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 1, 0])

  def testFilterBySingleLessThanAge(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter(age__lt=27).IsValid() for i in self.items],
                     [0, 0, 0, 0, 0, 0, 0, 0, 0])

  def testFilterBySingleLessThanAgeUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', age__lt=27).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 0, 0, 0])

  def testFilterBySingleLessThanAgeSecond(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(age__lt=31).IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 1, 1, 0])

  def testFilterBySingleLessThanAgeSecondUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', age__lt=31).IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 1, 1, 0])

  def testFilterByMultipleLessThan(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='us', age__lt=29).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleLessThanWithChaining(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='us').Filter(age__lt=29).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleLessThanUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name='us', age__lt=29).IsValid() for i in self.items],
        [1, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterByMultipleWithTupleLessThan(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter(name=t, age__lt=29).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 0, 0])

  def testFilterByMultipleWithTupleLessThanWithChaining(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter(name=t).Filter(age__lt=29).IsValid() for i in self.items],
        [0, 0, 1, 1, 0, 0, 1, 0, 0])

  def testFilterByMultipleWithTupleLessThanUsingOrMode(self):
    """Tests that the correct result is returned."""
    t = ('base', 'us')
    self.assertEqual(
        [i.Filter('OR', name=t, age__lt=29).IsValid() for i in self.items],
        [1, 0, 1, 1, 0, 0, 1, 1, 1])

  def testFilterBySingleLessThanOrEqualToAge(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter(age__lte=27).IsValid() for i in self.items],
                     [1, 0, 1, 0, 0, 0, 1, 0, 0])

  def testFilterBySingleLessThanOrEqualToAgeUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', age__lte=27).IsValid() for i in self.items],
        [1, 0, 1, 0, 0, 0, 1, 0, 0])

  def testFilterByMultipleLessThanOrEqualTo(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='base', age__lte=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleLessThanOrEqualToWithChaining(self):
    """Tests that the correct result is returned."""
    n = 'base'
    self.assertEqual(
        [i.Filter(name=n).Filter(age__lte=27).IsValid() for i in self.items],
        [0, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleWithTupleLessThanOrEqualTo(self):
    """Tests that the correct result is returned."""
    t = ('base', 'all')
    self.assertEqual(
        [i.Filter(name=t, age__lte=27).IsValid() for i in self.items],
        [1, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleWithTupleLessThanOrEqualToWithChaining(self):
    """Tests that the correct result is returned."""
    tup = ('base', 'all')
    self.assertEqual(
        [i.Filter(name=tup).Filter(age__lte=27).IsValid() for i in self.items],
        [1, 0, 1, 0, 0, 0, 0, 0, 0])

  def testFilterByMultipleWithTupleLessThanOrEqualToUsingOrMode(self):
    """Tests that the correct result is returned."""
    t_t = ('base', 'all')
    self.assertEqual(
        [i.Filter('OR', name=t_t, age__lte=27).IsValid() for i in self.items],
        [1, 0, 1, 1, 0, 0, 1, 0, 0])

  def testFilterBySingleNotEqualTo(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name__ne='us').IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 0, 0, 0])

  def testFilterBySingleNotEqualToUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name__ne='us').IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 0, 0, 0])

  def testFilterByMultipleNotEqualTo(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name__ne='us', age__ne=30).IsValid() for i in self.items],
        [1, 0, 1, 1, 1, 1, 0, 0, 0])

  def testFilterByMultipleNotEqualToWithChaining(self):
    """Tests that the correct result is returned."""
    n = 'us'
    a = 30
    self.assertEqual(
        [i.Filter(name__ne=n).Filter(age__ne=a).IsValid() for i in self.items],
        [1, 0, 1, 1, 1, 1, 0, 0, 0])

  def testFilterByMultipleNotEqualToUsingOrMode(self):
    """Tests that the correct result is returned."""
    n = 'us'
    a = 30
    self.assertEqual(
        [i.Filter('OR', name__ne=n, age__ne=a).IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 1, 0, 1])

  def testFilterByMultipleWithTupleNotEqual(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name__ne=('us', 'base')).IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 1, 1, 1])

  def testFilterBySingleGreaterThanOrEqualToAgeFirst(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(age__gte=27).IsValid() for i in self.items],
        [1, 1, 1, 1, 1, 1, 1, 1, 1])

  def testFilterBySingleGreaterThanOrEqualToAgeSecond(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(age__gte=30).IsValid() for i in self.items],
        [0, 1, 0, 0, 0, 0, 0, 1, 1])

  def testFilterBySingleGreaterThanOrEqualToDateFirst(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(3, 3, 3)
    self.assertEqual(
        [i.Filter(date__gte=dt).IsValid() for i in self.items],
        [0, 1, 1, 1, 1, 1, 1, 1, 1])

  def testFilterBySingleGreaterThanOrEqualToDateSecond(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual(
        [i.Filter(date__gte=dt).IsValid() for i in self.items],
        [0, 1, 1, 0, 0, 0, 1, 1, 1])

  def testFilterByMultipleGreaterThanOrEqualTo(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='us', age__gte=30).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 0, 1, 1])

  def testFilterByMultipleGreaterThanOrEqualToWithChaining(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='us').Filter(age__gte=30).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 0, 1, 1])

  def testFilterByMultipleGreaterThanOrEqualToUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name='us', age__gte=30).IsValid() for i in self.items],
        [0, 1, 0, 0, 0, 0, 1, 1, 1])

  def testFilterByMultipleGreaterThanOrEqualToSecond(self):
    """Tests that the correct result is returned."""
    d = datetime.date(5, 5, 5)
    n = 'us'
    self.assertEqual(
        [i.Filter(name=n, date=d, age__gte=30).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 0, 1, 0])

  def testFilterByMultipleGreaterThanOrEqualToSecondUsinOrMode(self):
    """Tests that the correct result is returned."""
    dt = datetime.date(5, 5, 5)
    self.assertEqual([i.Filter(
        'OR', name='us', date=dt, age__gte=30).IsValid() for i in self.items],
                     [0, 1, 1, 0, 0, 0, 1, 1, 1])

  def testFilterByMultipleWithTupleGreaterThanOrEqualTo(self):
    """Tests that the correct result is returned."""
    t = ('us', 'base')
    self.assertEqual(
        [i.Filter(name=t, age__gte=28).IsValid() for i in self.items],
        [0, 0, 0, 1, 0, 0, 0, 1, 1])

  def testFilterByMultipleWithTupleGreaterThanOrEqualToUsingOrMode(self):
    """Tests that the correct result is returned."""
    t = ('us', 'base')
    self.assertEqual(
        [i.Filter('OR', name=t, age__gte=30).IsValid() for i in self.items],
        [0, 1, 1, 1, 0, 0, 1, 1, 1])

  def testFilterBySingleGreaterThan(self):
    """Tests that the correct result is returned."""
    self.assertEqual([i.Filter(age__gt=30).IsValid() for i in self.items],
                     [0, 0, 0, 0, 0, 0, 0, 0, 1])

  def testFilterBySingleGreaterThanUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', age__gt=30).IsValid() for i in self.items],
        [0, 0, 0, 0, 0, 0, 0, 0, 1])

  def testFilterByMultipleGreaterThan(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(name='base', age__gt=27).IsValid() for i in self.items],
        [0, 0, 0, 1, 0, 0, 0, 0, 0])

  def testFilterByMultipleGreaterThanWithChaining(self):
    """Tests that the correct result is returned."""
    n = 'base'
    self.assertEqual(
        [i.Filter(name=n).Filter(age__gt=27).IsValid() for i in self.items],
        [0, 0, 0, 1, 0, 0, 0, 0, 0])

  def testFilterByMultipleGreaterThanUsingOrMode(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter('OR', name='base', age__gt=27).IsValid() for i in self.items],
        [0, 1, 1, 1, 1, 1, 0, 1, 1])

  def testFilterByMultipleWithTupleGreaterThan(self):
    """Tests that the correct result is returned."""
    t = ('base', 'are', 'all')
    self.assertEqual(
        [i.Filter(name=t, age__gt=27).IsValid() for i in self.items],
        [0, 0, 0, 1, 1, 0, 0, 0, 0])

  def testFilterByMultipleWithTupleGreaterThanWithChaining(self):
    """Tests that the correct result is returned."""
    t = ('base', 'are', 'all')
    self.assertEqual(
        [i.Filter(name=t).Filter(age__gt=27).IsValid() for i in self.items],
        [0, 0, 0, 1, 1, 0, 0, 0, 0])

  def testFilterByMultipleWithTupleGreaterThanUsingOrMode(self):
    """Tests that the correct result is returned."""
    t = ('us', 'all')
    self.assertEqual(
        [i.Filter('OR', name=t, age__gt=27).IsValid() for i in self.items],
        [1, 1, 0, 1, 1, 1, 1, 1, 1])

  def testFilterByMultipleWithMultipleInequalities(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(age__gt=27, age__lt=31).IsValid() for i in self.items],
        [0, 1, 0, 1, 1, 1, 0, 1, 0])

  def testFilterByMultipleWithMultipleInequalitiesWithChaining(self):
    """Tests that the correct result is returned."""
    self.assertEqual(
        [i.Filter(age__gt=27).Filter(age__lt=31).IsValid() for i in self.items],
        [0, 1, 0, 1, 1, 1, 0, 1, 0])

  def testFilterByMultipleWithMultipleInequalitiesSecond(self):
    """Tests that the correct result is returned."""
    date = datetime.date(3, 3, 3)
    self.assertEqual(
        [i.Filter(date__gte=date, age__lt=31).IsValid() for i in self.items],
        [0, 1, 1, 1, 1, 1, 1, 1, 0])

  def testFilterByMultipleWithMultipleInequalitiesSecondWithChaining(self):
    """Tests that the correct result is returned."""
    d = datetime.date(3, 3, 3)
    v = 31
    self.assertEqual(
        [i.Filter(date__gte=d).Filter(age__lt=v).IsValid() for i in self.items],
        [0, 1, 1, 1, 1, 1, 1, 1, 0])

  def testFilterBySingleRaisesErrorWithSingleUnderscore(self):
    """Tests that the correct exception is raised."""
    item = self.items[0]
    self.assertRaises(easy_filter.InvalidEasyFilterKeywordArgument, item.Filter,
                      date_gte=datetime.date(1, 1, 1))

  def testFilterBySingleRaisesErrorWithThreeUnderscores(self):
    """Tests that the correct exception is raised."""
    item = self.items[0]
    self.assertRaises(easy_filter.InvalidEasyFilterKeywordArgument, item.Filter,
                      age___gte=1)

  def testFilterBySingleRaisesErrorWithBadAttributeName(self):
    """Tests that the correct exception is raised."""
    item = self.items[0]
    self.assertRaises(easy_filter.InvalidEasyFilterKeywordArgument, item.Filter,
                      nam='jason')

  def testFilterBySingleRaisesErrorWithBadAttributeNameWithInequality(self):
    """Tests that the correct exception is raised."""
    item = self.items[0]
    self.assertRaises(easy_filter.InvalidEasyFilterKeywordArgument, item.Filter,
                      ag__gte=34)

  def testFilterBySingleRaisesErrorWithBadAttributeWithTuple(self):
    """Tests that the correct exception is raised."""
    item = self.items[0]
    self.assertRaises(
        easy_filter.InvalidEasyFilterKeywordArgument, item.Filter, foo=(29, 30))

  def testFilterByAgeWithZeroGreaterThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = 0
    self.assertTrue(self.a.Filter(age__gte=0).IsValid())

  def testFilterByAgeWithZeroLessThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = 0
    self.assertTrue(self.a.Filter(age__lte=0).IsValid())

  def testFilterByAgeWithZeroLessThan(self):
    """Tests that a result is returned."""
    self.a.age = 0
    self.assertTrue(self.a.Filter(age__lt=1).IsValid())

  def testFilterByAgeWithZeroGreaterThan(self):
    """Tests that a result is returned."""
    self.a.age = 0
    self.assertTrue(self.a.Filter(age__gt=-1).IsValid())

  def testFilterByAgeWithZeroNotEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = 0
    self.assertTrue(self.a.Filter(age__ne=-2).IsValid())

  def testFilterByNameWithEmptyStringGreaterThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.name = ''
    self.assertTrue(self.a.Filter(name__gte='').IsValid())

  def testFilterByNameWithEmptyStringLessThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.name = ''
    self.assertTrue(self.a.Filter(name__lte='').IsValid())

  def testFilterByNameWithEmptyStringLessThan(self):
    """Tests that a result is returned."""
    self.a.name = ''
    self.assertTrue(self.a.Filter(name__lt='a').IsValid())

  def testFilterByNameWithEmptyStringGreaterThan(self):
    """Tests that a result is returned."""
    self.a.name = ''
    self.assertTrue(self.a.Filter(name__gt=None).IsValid())

  def testFilterByNameWithEmptyStringNotEqualTo(self):
    """Tests that a result is returned."""
    self.a.name = ''
    self.assertTrue(self.a.Filter(name__ne=[]).IsValid())

  def testFilterByDateWithNoneGreaterThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.date = None
    self.assertTrue(self.a.Filter(date__gte=None).IsValid())

  def testFilterByDateWithNoneLessThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.date = None
    self.assertTrue(self.a.Filter(date__lte=None).IsValid())

  def testFilterByDateWithNoneLessThan(self):
    """Tests that a result is returned."""
    self.a.date = None
    self.assertTrue(self.a.Filter(date__lt=-1).IsValid())

  def testFilterByDateWithNoneGreaterThan(self):
    """Tests that a result is returned."""
    self.a.date = None
    self.assertFalse(self.a.Filter(date__gt=False).IsValid())

  def testFilterByDateWithNoneNotEqualTo(self):
    """Tests that a result is returned."""
    self.a.date = None
    self.assertTrue(self.a.Filter(date__ne=False).IsValid())

  def testFilterByAgeWithFalseGreaterThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = False
    self.assertTrue(self.a.Filter(age__gte=False).IsValid())

  def testFilterByAgeWithFalseLessThanOrEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = False
    self.assertTrue(self.a.Filter(age__lte=True).IsValid())

  def testFilterByAgeWithFalseLessThan(self):
    """Tests that a result is returned."""
    self.a.age = False
    self.assertTrue(self.a.Filter(age__lt=1).IsValid())

  def testFilterByAgeWithFalseGreaterThan(self):
    """Tests that a result is returned."""
    self.a.age = False
    self.assertFalse(self.a.Filter(age__gt=True).IsValid())

  def testFilterByAgeWithFalseNotEqualTo(self):
    """Tests that a result is returned."""
    self.a.age = False
    self.assertTrue(self.a.Filter(age__ne=None).IsValid())


class Foo(easy_filter.EasyFilter):
  """Test helper class used for unit testing the EasyFilter class.

  Attributes:
    name: String name.
    date: Date object date.
    time: Datetime object time.
    age: Integer age.
  """

  def __init__(self, name, date, time, age):
    """Initalizes the Foo class.

    Args:
      name: String name.
      date: Date object date.
      time: Datetime object time.
      age: Integer age.
    """
    easy_filter.EasyFilter.__init__(self)
    self.name = name
    self.date = date
    self.time = time
    self.age = age


if __name__ == '__main__':
  unittest.main()
